#include "stdafx.h"
/////////////////////////////////////////////////////////////////////////////
class write_cache wtcache;
/////////////////////////////////////////////////////////////////////////////
write_cache::write_cache(void):
	__items__(NULL),__end__(NULL),__files__(NULL),last_minute(0)
{
	InitializeCriticalSection(&__cs_cache__);
	InitializeCriticalSection(&__cs_file__);
}

write_cache::~write_cache(void)
{
	DeleteCriticalSection(&__cs_cache__);
	DeleteCriticalSection(&__cs_file__);
}
/////////////////////////////////////////////////////////////////////////////
void write_cache::register_file(safe_file*pfile)
{
	EnterCriticalSection(&__cs_file__);
	pfile->pnext = __files__;
	__files__ = pfile;
	LeaveCriticalSection(&__cs_file__);
}

void write_cache::unregister_file(safe_file*pfile)
{
	safe_file*pList=NULL,*pLast=NULL;
	EnterCriticalSection(&__cs_file__);
	for(pList=__files__;pList;pList=(pLast=pList)->pnext)
	{
		if(pList==pfile)
		{
			(pLast?pLast->pnext:__files__) = pList->pnext;
			break;
		}
	}
	LeaveCriticalSection(&__cs_file__);
}
/////////////////////////////////////////////////////////////////////////////
BOOL write_cache::register_cache(safe_file*pfile,DWORD offset,DWORD size,LPCVOID buffer)
{
	PITEM pItem=(PITEM)zwl_memory_malloc(sizeof(ITEM)+size);
	if(!pItem) return(FALSE);
	pItem->pfile = pfile;
	pItem->offset = offset;
	pItem->size = size;
	pItem->pnext = NULL;
	memcpy(pItem->buffer,buffer,size);
	EnterCriticalSection(&__cs_cache__);
	(__end__?__end__->pnext:__items__) = pItem;
	__end__ = pItem;
	LeaveCriticalSection(&__cs_cache__);
	return(TRUE);
}

long write_cache::write_direct(long num)
{
	long i(0);
	PITEM pItem=NULL;
	for(;i<num;++i)
	{
		pItem=NULL;
		EnterCriticalSection(&__cs_cache__);
		if(__items__)
		{
			pItem = __items__;
			if(__items__==__end__) __end__ = NULL;
			__items__ = __items__->pnext;
		}
		else
		{
			LeaveCriticalSection(&__cs_cache__);
			break;
		}
		LeaveCriticalSection(&__cs_cache__);
		pItem->pfile->WriteToFile(pItem->buffer,pItem->offset,pItem->size,TRUE);
		zwl_memory_release((LPSTR&)pItem);
	}
	return(i);
}

void write_cache::timeslice(void)
{
	if(write_direct(10)<1)
	{
		_interval = 300;
	}
	else
	{
		_interval = 1;
	}
}
